package main1;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * @author zhx
 * @since 2020-08-07
 */
public class MultiThread1 {
    static Lock lock = new ReentrantLock();
    static volatile int count = 0;

    public static void main(String[] args) {


        List<Thread> threadList = new ArrayList<>();
        List<Condition> conditionList = new ArrayList<>();
//        boolean[] flag = new boolean[100];
        for (int i = 0; i < 100; i++) {
            conditionList.add(lock.newCondition());
        }
        for (int i = 0; i < 100; i++) {
            int finalI = i;
            threadList.add(new Thread(() -> {
                lock.lock();
                try {
                    if (finalI > 0) {
                        while (finalI != count) {
                            conditionList.get(finalI).await();
                        }
                    }
                    System.out.println(Thread.currentThread().getName() + "------------>" + (finalI + 1));
                    if (finalI + 1 < 100) {
                        count++;
                        conditionList.get(finalI + 1).signal();
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                } finally {
                    lock.unlock();
                }
            }));
        }
        for (int i = 0; i < 100; i++) {
            threadList.get(i).start();
        }
    }
}

class CountDown {
    static Lock lock = new ReentrantLock();

    public static void main(String[] args) {
        CountDownLatch latch = new CountDownLatch(100);

        List<Thread> threadList = new ArrayList<>();
        for (int i = 0; i < 100; i++) {
            int finalI = i;
            threadList.add(new Thread(() -> {
                lock.lock();
                try {
                    if (finalI > 0) {
                        while (100 - latch.getCount() + 1 != finalI) {
                            try {
                                System.out.println(Thread.currentThread().getName() + " waiting");
                                latch.await();
                            } catch (InterruptedException e) {
                                e.printStackTrace();
                            }
                        }
                        System.out.println(Thread.currentThread().getName() + "------------>" + (finalI + 1));
                        if (100 - latch.getCount() > 0) {
                            latch.countDown();
                        }
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                } finally {
                    lock.unlock();
                }
            }));
        }
        for (int i = 0; i < 100; i++) {
            threadList.get(i).start();
        }
    }
}


